﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Text;
using System.Windows.Forms;
using DevExpress.XtraEditors;
using DevExpress.XtraBars;
using System.Linq;
using ProductManager.bl;
namespace ProductManager.gui
{
    public partial class GUIProduct : DevExpress.XtraEditors.XtraForm
    {

        private IEnumerable<AllProduct> listProduct = null;
        private Product product = null;
        private ProductMDDataContext ctx = null;
        private BLProduct blProduct = null;
        private int status = 0;
        private string sname = "";
        private decimal fsprice = 0;
        private decimal tsprice = 0;

        private int currentpage = 0;
        private int totalpage = 0;
        private int pageSize = 10;

        private string search = "";
       

        public GUIProduct()
        {
            InitializeComponent();
            RefreshData();
        }


        public GUIProduct(string search, int type)
        {
            InitializeComponent();
            this.search = search;
            RefreshData(search, type);
        }


        private void GUIProduct_Load(object sender, EventArgs e)
        {
            ctx = new ProductMDDataContext();
            blProduct = new BLProduct();
            cboSearch.SelectedIndex = 0;
            txtToPrice.Visible = false;
            txtFromPrice.Visible = false;
            lblFrom.Visible = false;
            lblTo.Visible = false;
            txtProductID.Properties.ReadOnly = true;
            cboSearch.Properties.TextEditStyle = DevExpress.XtraEditors.Controls.TextEditStyles.DisableTextEditor;
            cboCompany.Properties.TextEditStyle = DevExpress.XtraEditors.Controls.TextEditStyles.DisableTextEditor;
            cboCategory.Properties.TextEditStyle = DevExpress.XtraEditors.Controls.TextEditStyles.DisableTextEditor;

        }


        private void ResetText()
        {
            txtProductID.Text = "";
            txtProductName.Text = "";
            txtPrice.Text = "";
            txtQuantity.Text = "";
            txtDescription.Text = "";
            cboCategory.SelectedIndex = 0;
            cboCompany.SelectedIndex = 0;
        }
        //RefreshData
        public void RefreshData()
        {
            try
            {
                status = 0;
                ctx = new ProductMDDataContext();
                var list = ctx.AllProducts;
                listProduct = list.AsEnumerable();
                LoadData();
            }
            catch (Exception ex)
            {

            }
        }


        public void RefreshData(string search, int type)
        {
            try
            {
                ctx = new ProductMDDataContext();
                
                if (type == 1)
                {
                    status = 3;
                    var list = ctx.AllProducts.Where(l => l.CategoryName == search);
                    listProduct = list.AsEnumerable();
                }
                else {
                    status = 4;
                    var list = ctx.AllProducts.Where(l => l.CompanyName == search);
                    listProduct = list.AsEnumerable();
                }

                this.search = search;

                LoadData();
            }
            catch (Exception ex)
            {

            }
        }



        public void loadCategory(){
            var category = ctx.Categories.Where(c =>c.Status.Equals(true));
            cboCategory.Properties.Items.Clear();
            foreach (Category c in category)
            {
                cboCategory.Properties.Items.Add(c.CategoryName);
            }

 
        }

        public void loadCompany() {
            var company = ctx.Companies.Where(c => c.Status.Equals(true));
            cboCompany.Properties.Items.Clear();
            foreach (Company c in company)
            {
                cboCompany.Properties.Items.Add(c.CompanyName);
            }
        }
        public void LoadData()
        {
            try
            {
                loadCategory();
                loadCompany();
                CreatePage();
                ResetText();
                btnUpdate.Enabled = false;  
                btnDelete.Enabled = false;
                btnAdd.Enabled = false;
            }
            catch (Exception ex)
            {

            }
        }

        private void LoadDataCurrent(IEnumerable<AllProduct> data)
        {
            

            grvProduct.Columns.Clear();
            grvProduct.AutoGenerateColumns = false;
            grvProduct.AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.Fill;
            DataGridViewCell cell = new DataGridViewTextBoxCell();

            DataGridViewColumn columnID = new DataGridViewColumn();
            columnID.HeaderText = "ID";
            columnID.Name = "ID";
            columnID.Visible = true;
            columnID.ReadOnly = true;
            columnID.CellTemplate = cell;
            columnID.DataPropertyName = "ProductID";

            DataGridViewColumn columnCategoryName = new DataGridViewColumn();
            columnCategoryName.HeaderText = "Category Name";
            columnCategoryName.Name = "Category Name";
            columnCategoryName.Visible = true;
            columnCategoryName.ReadOnly = true;
            columnCategoryName.CellTemplate = cell;
            columnCategoryName.DataPropertyName = "CategoryName";

            DataGridViewColumn columnCompanyName = new DataGridViewColumn();
            columnCompanyName.HeaderText = "Company Name";
            columnCompanyName.Name = "Company Name";
            columnCompanyName.Visible = true;
            columnCompanyName.ReadOnly = true;
            columnCompanyName.CellTemplate = cell;
            columnCompanyName.DataPropertyName = "CompanyName";

            DataGridViewColumn columnName = new DataGridViewColumn();
            columnName.HeaderText = "Product Name";
            columnName.Name = "Name";
            columnName.Visible = true;
            columnName.ReadOnly = true;
            columnName.CellTemplate = cell;
            columnName.DataPropertyName = "ProductName";

            DataGridViewColumn columnPrice = new DataGridViewColumn();
            columnPrice.HeaderText = "Price";
            columnPrice.Name = "Price";
            columnPrice.Visible = true;
            columnPrice.ReadOnly = true;
            columnPrice.CellTemplate = cell;
            columnPrice.DataPropertyName = "Price";

            DataGridViewColumn columnQuantity = new DataGridViewColumn();
            columnQuantity.HeaderText = "Quantity";
            columnQuantity.Name = "Quantity";
            columnQuantity.Visible = true;
            columnQuantity.ReadOnly = true;
            columnQuantity.CellTemplate = cell;
            columnQuantity.DataPropertyName = "Quantity";

            DataGridViewColumn columnDescription = new DataGridViewColumn();
            columnDescription.HeaderText = "Descirption";
            columnDescription.Name = "Description";
            columnDescription.Visible = true;
            columnDescription.ReadOnly = true;
            columnDescription.CellTemplate = cell;
            columnDescription.DataPropertyName = "Description";

            grvProduct.Columns.Add(columnID);
            grvProduct.Columns.Add(columnCategoryName);
            grvProduct.Columns.Add(columnCompanyName);
            grvProduct.Columns.Add(columnName);
            grvProduct.Columns.Add(columnPrice);
            grvProduct.Columns.Add(columnQuantity);
            grvProduct.Columns.Add(columnDescription);

            grvProduct.DataSource = data;
        }



        private void grvProduct_CellClick(object sender, DataGridViewCellEventArgs e)
        {
            try
            {

                DataGridViewRow row = grvProduct.Rows[e.RowIndex];
                int id = 0;
                id = Convert.ToInt32(row.Cells[0].Value.ToString());
                if (id > 0)
                {
                    product = ctx.Products.Single(p => p.ProductID == id);
                    txtProductID.Text = product.ProductID.ToString();
                    txtProductName.Text = product.ProductName;
                    txtQuantity.Text = product.Quantity.ToString();
                    txtPrice.Text = product.Price.ToString();
                    txtDescription.Text = product.Description;

                    Category cate = ctx.Categories.Single(c => c.CategoryID == product.CategoryID);
                    cboCategory.SelectedItem = cate.CategoryName;

                    Company com = ctx.Companies.Single(c => c.CompanyID == product.CompanyID);
                    cboCompany.SelectedItem = com.CompanyName;
                    btnDelete.Enabled = true;
                    btnUpdate.Enabled = true;
                    btnAdd.Enabled = false;
                }
            }
            catch (Exception ex)
            {

            }
        }

        private void btnList_Click(object sender, EventArgs e)
        {
            RefreshData();
        }

        private void btnDelete_Click(object sender, EventArgs e)
        {
            DialogResult result = MessageBox.Show(this, "Do you want to delete " + product.ProductName + " ?", "Delete", MessageBoxButtons.YesNo, MessageBoxIcon.Question);
            if (result == DialogResult.Yes)
            {
                if (product != null)
                {
                    ctx.Products.DeleteOnSubmit(product);
                }
                ctx.SubmitChanges();
                MessageBox.Show(this, "Delete successful", "Delete Result", MessageBoxButtons.OK, MessageBoxIcon.Information);
                RefreshData();
            }
        }

        private void btnUpdate_Click(object sender, EventArgs e)
        {
            DialogResult result = MessageBox.Show(this, "Do you want to update " + product.ProductName + " ?", "Update", MessageBoxButtons.YesNo, MessageBoxIcon.Question);
            if (result == DialogResult.Yes)
            {
                if (product != null)
                {
                    if (blProduct.ValidateAdd(txtProductName.Text, txtPrice.Text, txtQuantity.Text))
                    {
                        product.ProductName = txtProductName.Text;
                        product.Price = Convert.ToDecimal(txtPrice.Text);
                        product.Quantity = Convert.ToInt32(txtQuantity.Text);
                        product.Description = txtDescription.Text;
                        product.CategoryID = ctx.Categories.Single(c => c.CategoryName == cboCategory.SelectedItem).CategoryID;
                        product.CompanyID = ctx.Companies.Single(c => c.CompanyName == cboCompany.SelectedItem).CompanyID;
                        ctx.SubmitChanges();
                    }
                }
                ctx.SubmitChanges();
                MessageBox.Show(this, "Update successful", "Update Result", MessageBoxButtons.OK, MessageBoxIcon.Information);
                RefreshData();
            }
        }

        private void btnAdd_Click(object sender, EventArgs e)
        {
            if (blProduct.ValidateAdd(txtQuantity.Text, txtPrice.Text, txtQuantity.Text))
            {
                product = new Product();
                product.ProductName = txtProductName.Text;
                product.Price = Convert.ToDecimal(txtPrice.Text);
                product.Quantity = Convert.ToInt32(txtQuantity.Text);
                product.Description = txtDescription.Text;
                product.CategoryID = ctx.Categories.Single(c => c.CategoryName == cboCategory.SelectedItem).CategoryID;
                product.CompanyID = ctx.Companies.Single(c => c.CompanyName == cboCompany.SelectedItem).CompanyID;
                product.Status = true;
                
                ctx.add_Product(product.CategoryID, product.CompanyID, product.ProductName, product.Price, product.Quantity, product.Description, product.Status);
                ctx.SubmitChanges();
                MessageBox.Show(this, "Add successful", "Add Result", MessageBoxButtons.OK, MessageBoxIcon.Information);
                RefreshData();
                btnAdd.Enabled = false;
            }
        }

        private void btnNew_Click(object sender, EventArgs e)
        {
            ResetText();
            btnUpdate.Enabled = false;
            btnDelete.Enabled = false;
            btnAdd.Enabled = true;
        }

        private void btnSearch_Click(object sender, EventArgs e)
        {
            int selected = cboSearch.SelectedIndex;

            if (selected == 0)
            {
                if (blProduct.ValidateSearchByName(txtSearchName.Text))
                {
                    if (ctx != null)
                    {
                        status = 1;
                        sname = txtSearchName.Text;
                        var list = ctx.AllProducts.Where(p => p.ProductName.Contains(sname));
                        listProduct = list.AsEnumerable();
                        LoadData();

                        if (listProduct.Count() == 0)
                        {
                            MessageBox.Show(this, "No items match your search!", "Search Result", MessageBoxButtons.OK, MessageBoxIcon.Information);
                        }
                        else
                        {
                            //LoadData();
                        }
                    }
                }
                else
                {
                    //
                }

            }
            if (selected == 1)
            {
                if (blProduct.ValidateSearchByPrice(txtFromPrice.Text, txtToPrice.Text))
                {
                    if (ctx != null)
                    {
                        status = 2;
                        fsprice = Convert.ToDecimal(txtFromPrice.Text);
                        tsprice = Convert.ToDecimal(txtToPrice.Text);

                        var list = ctx.AllProducts.Where(p => (p.Price >= fsprice && p.Price <= tsprice));
                        listProduct = list.AsEnumerable();
                        LoadData();

                        if (listProduct.Count() == 0)
                        {
                            MessageBox.Show(this, "No items match your search!", "Search Result", MessageBoxButtons.OK, MessageBoxIcon.Information);
                            
                        }
                        else
                        {
                            //LoadData();
                        }
                    }
                }
                else
                {
                    // MessageBox.Show(this, "No items match your search!", "Search Result", MessageBoxButtons.OK, MessageBoxIcon.Information);
                }
            }
        }

        private void cboSearch_SelectedIndexChanged(object sender, EventArgs e)
        {
            if (cboSearch.SelectedIndex == 0)
            {
                txtToPrice.Visible = false;
                txtFromPrice.Visible = false;
                lblFrom.Visible = false;
                lblTo.Visible = false;
                txtSearchName.Visible = true;
            }

            if (cboSearch.SelectedIndex == 1)
            {
                txtToPrice.Visible = true;
                txtFromPrice.Visible = true;
                lblFrom.Visible = true;
                lblTo.Visible = true;
                txtSearchName.Visible = false;
            }
        }


        //==============================================//
        //        Pagination with sql and linq          //
        //==============================================//
        private void CreatePage()
        {
            currentpage = 0;
            if (listProduct.Count() % pageSize == 0)
            {
                totalpage = listProduct.Count() / pageSize;
            }
            else
            {
                totalpage = listProduct.Count() / pageSize + 1;
            }

            lblTotalPage.Caption = "Total page: " + totalpage.ToString();
            lblTotalProduct.Caption = "Total Product: " + listProduct.Count().ToString();

            

            if (totalpage != 0)
            {
                GoToPage(0);
            }
            else
            {
                grvProduct.Columns.Clear();
                barbtnFirst.Enabled = false;
                barbtnLast.Enabled = false;
                barbtnNext.Enabled = false;
                barbtnPrevious.Enabled = false;
                barbtnPreviousPage.Enabled = false;
                barbtnNextPage.Enabled = false;
            }

        }

        

        private void GoToPage(int page)
        {
            currentpage = page;
            if (status == 0)
            {
                LoadDataCurrent(ctx.AllProducts.Skip(currentpage * pageSize).Take(pageSize));
            }
            else
            {
                if (status == 1)
                {
                    var list1 = ctx.AllProducts.Where(p => p.ProductName.Contains(sname)).Skip(currentpage * pageSize).Take(pageSize);
                    LoadDataCurrent(list1);
                }
                 else if(status == 2)
                {
                    var list2 = ctx.AllProducts.Where(p => (p.Price >= fsprice && p.Price <= tsprice)).Skip(currentpage * pageSize).Take(pageSize);
                    LoadDataCurrent(list2);
                }
                else if (status == 3)
                {
                    var list3 = ctx.AllProducts.Where(p => p.CategoryName == (search)).Skip(currentpage * pageSize).Take(pageSize);
                    LoadDataCurrent(list3);
                }
                else {
                    var list4 = ctx.AllProducts.Where(p => p.CompanyName == (search)).Skip(currentpage * pageSize).Take(pageSize);
                    LoadDataCurrent(list4);
                }

            }


            if (currentpage == 0)
            {
                barbtnFirst.Enabled = false;
                barbtnPrevious.Enabled = false;
            }
            else
            {
                barbtnFirst.Enabled = true;
                barbtnPrevious.Enabled = true;
            }

            if (currentpage == totalpage - 1)
            {
                barbtnNext.Enabled = false;
                barbtnLast.Enabled = false;
            }
            else
            {
                barbtnNext.Enabled = true;
                barbtnLast.Enabled = true;
            }

            if ((currentpage - 5) < 0)
            {
                barbtnPreviousPage.Enabled = false;
            }
            else
            {
                barbtnPreviousPage.Enabled = true;
            }

            if ((currentpage + 5) > totalpage - 1)
            {
                barbtnNextPage.Enabled = false;
            }
            else
            {
                barbtnNextPage.Enabled = true;
            }
        }

        private void barbtnFirst_ItemClick(object sender, ItemClickEventArgs e)
        {
            GoToPage(0);
        }

        private void barbtnPreviousPage_ItemClick(object sender, ItemClickEventArgs e)
        {
            GoToPage(currentpage - 5);
        }

        private void barbtnPrevious_ItemClick(object sender, ItemClickEventArgs e)
        {
            GoToPage(currentpage - 1);
        }

        private void barbtnNext_ItemClick(object sender, ItemClickEventArgs e)
        {
            GoToPage(currentpage + 1);
        }

        private void barbtnNextPage_ItemClick(object sender, ItemClickEventArgs e)
        {
            GoToPage(currentpage + 5);
        }

        private void barbtnLast_ItemClick(object sender, ItemClickEventArgs e)
        {
            GoToPage(totalpage - 1);
        }
    }

}